package com.fsck.k9.widget;

import java.util.HashMap;

import android.app.PendingIntent;
import android.app.Service;
import android.appwidget.AppWidgetManager;
import android.appwidget.AppWidgetProvider;
import android.content.ComponentName;
import android.content.ContentResolver;
import android.content.Context;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.database.Cursor;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Rect;
import android.graphics.Paint.Style;
import android.net.Uri;
import android.os.IBinder;
import android.text.TextPaint;
import android.util.Log;
import android.widget.RemoteViews;

public class MailBoxCounter extends AppWidgetProvider {
    private static final String TAG = "AppWidgetProvider";
    private static final Integer DRAW_CIRCLE_BORDER_SIZE=2;
    

    @Override
    public void onUpdate(Context context, AppWidgetManager appWidgetManager,
            int[] appWidgetIds) {
        // To prevent any ANR timeouts, we perform the update in a service
        context.startService(new Intent(context, UpdateService.class));
    }

    public static class UpdateService extends Service {
        @Override
        public void onStart(Intent intent, int startId) {
            // Build the widget update for today
            buildUpdateAll(this.getApplicationContext(),intent);
        }

       
        static HashMap<String,Integer> fetchNewMailAccounts(Context context, Account account)
        {
    		ContentResolver cr = context.getContentResolver();
    		HashMap<String,Integer> allNewMailAccounts=new HashMap<String,Integer>();
    		
    		Uri uri=Uri.parse("content://com.fsck.k9.messageprovider/accounts");
    		Log.d("MailBoxCounter", "uri=" + uri.toString());
    		final Cursor cur=cr.query(uri, null, null, null, null);
    		if(cur!=null)
    		{
	    		Log.d("MailBoxCounter", "Number of accounts=" + cur.getCount());
	    		if(cur.moveToFirst())
	    			do
	    			{
	    				Log.d("MailBoxCounter", "Account=" + cur.getString(1)+"/"+cur.getInt(0));
	    				if(account==null || cur.getString(2).equals(account.getUuid()))
	    				{
		    				uri=Uri.parse("content://com.fsck.k9.messageprovider/account_unread/"+cur.getInt(0)+"/");
		    				Cursor unreadCur=cr.query(uri, null, null, null, null);
		    				unreadCur.moveToFirst();
		    				Log.d("MailBoxCounter", "Unread(s)=" + unreadCur.getInt(1));
		    				allNewMailAccounts.put(cur.getString(2), unreadCur.getInt(1));
		    				if(account!=null) break;
	    				}
	    			}            
	    			while(cur.moveToNext());
    		}
    		return allNewMailAccounts;
        
        }
        /**
         * Build a widget update to show the current Wiktionary
         * "Word of the day." Will block until the online API returns.
         */
        static public void buildUpdateAll(Context context,Intent intent) {
            Log.d("MailBoxCounter", "Full build update received");
            AppWidgetManager gm = AppWidgetManager.getInstance(context);
            int[] appWidgetIds =gm.getAppWidgetIds(new ComponentName(context, MailBoxCounter.class));
            HashMap<String,Integer> allNewMailAccounts=fetchNewMailAccounts(context,null);

            final int N = appWidgetIds.length;
            for (int i=0; i<N; i++) {
                Log.d("MailBoxCounter", "Updating widget: #"+i);
                gm.updateAppWidget(appWidgetIds[i], UpdateService.buildUpdate(context,appWidgetIds[i],allNewMailAccounts));
            }       
        }
        static public RemoteViews buildUpdate(Context context,Integer appWidgetId,  HashMap<String,Integer> cachedResults) {
            RemoteViews updateViews = null;


            // Build an update that holds the updated widget contents
            updateViews = new RemoteViews(context.getPackageName(), R.layout.widget_mail);

            Account widgetAccount = K9WidgetConfigure.loadTitlePref(context, appWidgetId);
            
            String allAccounts=context.getString(R.string.k9widget_mailbox_all);
            long nNewMail=0;

            if(cachedResults==null) cachedResults=fetchNewMailAccounts(context,widgetAccount==null || allAccounts.equals(widgetAccount)?null:widgetAccount);
            
            if(widgetAccount!=null && allAccounts.equals(widgetAccount)==false) 
            {
            	if(cachedResults.containsKey(widgetAccount.getUuid()))nNewMail=cachedResults.get(widgetAccount.getUuid());
            	else widgetAccount=null;
            }
            if(widgetAccount==null)
            {
	            for(Integer value: cachedResults.values())
	            	nNewMail+=value;
            }

            updateViews.setTextViewText(R.id.widget_text_account, widgetAccount!=null?widgetAccount.getAccountName():context.getString(R.string.k9widget_mailbox_all));


            {
            	Bitmap bitmap=BitmapFactory.decodeResource(context.getResources(), R.drawable.k9mail).copy(Bitmap.Config.ARGB_8888, true);
            	Canvas canvas=new Canvas(bitmap);
            	
            	if(nNewMail>0)
            	{
            		TextPaint p=new TextPaint();
	            	p.setAntiAlias(true);
	            	p.setStyle(Style.FILL);
	            	p.setStrokeWidth(1);
	            	p.setColor(Color.WHITE);
	            	
	            	Rect rect=new Rect();
	            	p.getTextBounds(String.valueOf(nNewMail), 0, String.valueOf(nNewMail).length(), rect);
	            	float textWidth=Math.abs(rect.right);
	            	float textHeight=Math.abs(rect.top);
	            	
	            	Log.d("alors",rect.toString());

	            	float greatestSize=(float)Math.hypot(textWidth, textHeight)+DRAW_CIRCLE_BORDER_SIZE*2;

	            	{
	            		Paint circleP=new Paint();
	            		circleP.setAntiAlias(true);
	            		circleP.setStyle(Style.FILL_AND_STROKE);
		            	p.setStrokeWidth(DRAW_CIRCLE_BORDER_SIZE);
	            		circleP.setColor(Color.WHITE);
		            	canvas.drawCircle(bitmap.getWidth()-(greatestSize/2), greatestSize/2, greatestSize/2, circleP);
	            		circleP.setStyle(Style.FILL);
	            		circleP.setColor(Color.RED);
		            	canvas.drawCircle(bitmap.getWidth()-(greatestSize/2), greatestSize/2, (greatestSize-DRAW_CIRCLE_BORDER_SIZE)/2, circleP);
	            	}
	            	canvas.drawText(String.valueOf(nNewMail), bitmap.getWidth()-greatestSize+(greatestSize-textWidth)/2, greatestSize-(greatestSize-textHeight)/2, p);
            	}
            	updateViews.setImageViewBitmap(R.id.widget_drawable_mailbox, bitmap);
            }

            final Intent defineIntent = new Intent();
            if(widgetAccount!=null)
           	{
            	defineIntent.putExtra("account", widgetAccount.getUuid());
            	defineIntent.putExtra("fromShortcut", true);
           	}
            defineIntent.setAction(Intent.ACTION_MAIN);
            defineIntent.addCategory(Intent.CATEGORY_LAUNCHER);
            defineIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_RESET_TASK_IF_NEEDED);
            defineIntent.setComponent(new ComponentName("com.fsck.k9",widgetAccount!=null?"com.fsck.k9.activity.FolderList":"com.fsck.k9.activity.Accounts"));
        
            final PendingIntent pendingIntent = PendingIntent.getActivity(context,
                0, defineIntent, 0 );
            updateViews.setOnClickPendingIntent(R.id.widget_mail, pendingIntent);

            return updateViews;
        }

        @Override
        public IBinder onBind(Intent intent) {
            // We don't need to bind to this service
            return null;
        }
    }

    @Override
    public void onDeleted(Context context, int[] appWidgetIds) {
        Log.d(TAG, "onDeleted");
        // When the user deletes the widget, delete the preference associated with it.
        final int N = appWidgetIds.length;
        for (int i=0; i<N; i++) {
        	K9WidgetConfigure.deleteTitlePref(context.getApplicationContext(),appWidgetIds[N]);
        }
    }

    @Override
    public void onEnabled(Context context) {
        Log.d(TAG, "onEnabled");
        // When the first widget is created, register for the TIMEZONE_CHANGED and TIME_CHANGED
        // broadcasts.  We don't want to be listening for these if nobody has our widget active.
        // This setting is sticky across reboots, but that doesn't matter, because this will
        // be called after boot if there is a widget instance for this provider.
        PackageManager pm = context.getPackageManager();
        pm.setComponentEnabledSetting(
                new ComponentName("com.fsck.k9.widget", "WidgetBroadcastReceiver"),
                PackageManager.COMPONENT_ENABLED_STATE_ENABLED,
                PackageManager.DONT_KILL_APP);
    }

    @Override
    public void onDisabled(Context context) {
        // When the first widget is created, stop listening for the TIMEZONE_CHANGED and
        // TIME_CHANGED broadcasts.
        Log.d(TAG, "onDisabled");
        PackageManager pm = context.getPackageManager();
        pm.setComponentEnabledSetting(
                new ComponentName("com.fsck.k9.widget", "WidgetBroadcastReceiver"),
                PackageManager.COMPONENT_ENABLED_STATE_ENABLED,
                PackageManager.DONT_KILL_APP);
    }

}